
#include "sparrow.h"
#include "tetris.h"
#include "oled/oled.h"

__attribute__((section(".text.init"))) 
void _start()
{
    uint32_t status;
    uint32_t state = 0;
    uint32_t rx_data;
    uint32_t dip;
    int c;

    __asm__ volatile (
                "li sp, 0x8ff0;\n"          //初始化栈指针
                ::: "memory");
 
    SSD_0 = 0;
    SSD_1 = 1;
    SSD_2 = 2;
    SSD_3 = 3;

    spr_printf("hello, world\n");

    oled_init();

/*
    oled_change_blk(1, 0, 1);
    oled_change_blk(0, 1, 1);
    oled_change_blk(1, 1, 1);
    oled_change_blk(2, 1, 1);
    oled_refresh();
    spr_delay(1000);
    oled_change_blk(1, 0, 0);
    oled_change_blk(0, 1, 0);
    oled_change_blk(1, 1, 0);
    oled_change_blk(2, 1, 0);
    oled_refresh();

*/

    tetris_game_loop(); 

    while (1) {
        dip = spr_get_dip_b();
        LED_B = dip;
        dip = spr_get_dip_c();
        LED_C = dip;
    }
}

uint32_t spr_get_dip_b(void)
{
    return DIP_B;
}

uint32_t spr_get_dip_c(void)
{
    return DIP_C;
}

int spr_get_ch(void)
{
    int c;
    if ((UART_STATUS & UART_ST_RX_EMPTY) == 0)
        c = UART_RX_REG;
    else
        c = -1;
    return c;
}

//延迟一小段时间
void spr_delay(unsigned int moments)
{
	unsigned char j;

	while(moments--) {
		for(j=0; j<12; j++)
            barrier();
	}
}

//输出单个字符
void spr_putc(char ch)
{
    spr_delay(100);
    while ((UART_STATUS & UART_ST_RX_FULL) == 1)
        barrier();
    UART_TX_REG = ch;
}

void spr_puts(char *msg)
{
    char *p = msg;

    while (*p != '\0') {
        spr_delay(100);
        while ((UART_STATUS & UART_ST_RX_FULL) == 1)
            barrier();
        UART_TX_REG = *p;
        p++;
    }
}

//打印输出函数，目前只支持%x, %c, %s, %%等几个格式
uint32_t spr_printf(char *fmt, ...)
{
    register uint32_t a1 __asm__("a1"); 
    register uint32_t a2 __asm__("a2"); 
    register uint32_t a3 __asm__("a3"); 
    register uint32_t a4 __asm__("a4"); 
    register uint32_t a5 __asm__("a5"); 
    register uint32_t a6 __asm__("a6"); 
    register uint32_t a7 __asm__("a7"); 
    uint32_t a[] = {a1, a2, a3, a4, a5, a6, a7};
    uint32_t arg;
    int i = 0;
    int j, d, ch;
    char *p = fmt;
    char *p1;
    
    while (*p != '\0') {
        if (*p != '%') {
            spr_putc(*p);
            if (*p == '\n')
                spr_putc('\r');
        } else {
            p++;
            if (*p == '\0')
                break;
            arg = a[i];
            i++;
            switch (*p) {
            case 'x':
                for (j = 28; j >= 0; j -= 4) {
                    d = (arg >> j) & 0x0f;
                    ch = (d < 10 ? ('0' + d) : ('a' - 10 + d));
                    spr_putc(ch);
                }
                break;
            case 'c':
                spr_putc(arg);
                break;
            case 's':
                p1 = (char *)arg;
                while (*p1) {
                    spr_putc(*p1);
                    p1++;
                }
                break;
            default:
                spr_putc(*p);
                break;
            }
        }
        p++;
    }

    return 0;
}

void spr_err(char *msg)
{
    spr_puts(msg);
}

// 静态变量保存种子状态
static uint32_t _rand_state = 0;

// 初始化随机数生成器
void spr_srand(uint32_t seed) 
{
    _rand_state = seed;
}

// 生成随机数（线性同余法）
uint32_t spr_rand(void) 
{
    // LCG参数（遵循POSIX标准）
    const uint32_t a = 1103515245;
    const uint32_t c = 12345;
    const uint32_t m = 0x7FFFFFFF; // 2^31-1

    // 计算下一个状态：X_{n+1} = (a * X_n + c) mod m
    _rand_state = (a * _rand_state + c) % m;
    return _rand_state;
}

